package com.hanxiaozhang.threadbase1ndedition.no9container.no4concurrentcontainer;

import java.util.Queue;
import java.util.concurrent.ConcurrentLinkedQueue;

/**
 * 功能描述: <br>
 * 〈并发队列〉
 * <p>
 * 它是线程安全的非阻塞队列，内部是单向链表。
 * 它使用CAS机制保证线程安全。
 * 它的性能比LinkedBlockingQueue高很多。
 * 并发的情况下，替代LinkedList队列。
 * 注意:
 * i.ConcurrentLinkedQueue的头节点和尾节点都具有滞后性，直接读取不应当准确，不能直接使用，一般需要遍历。
 * ii.判断队列为空时，使用queue.isEmpty()，而不是queue.size()==0
 * <p>
 * https://zhuanlan.zhihu.com/p/130445195
 *
 * @Author:hanxinghua
 * @Date: 2021/11/21
 */
public class No5ConcurrentLinkedQueue {

    public static void main(String[] args) {

        ConcurrentLinkedQueue<String> queue = new ConcurrentLinkedQueue<>();
        // 这里add()直接使用的是offer()
        queue.add("a1");
        queue.add("a2");
        queue.add("a3");
        // offer()方法使用cas机制添加保证线程安全
        queue.offer("a3");
        System.out.println("队列元素：" + queue);

        System.out.println("队列元素个数：" + queue.size());
        // 弹出一个元素
        System.out.println("弹出一个元素：" + queue.poll());
        // size()方法底层使用的循环，队列元素越多，方法执行时间越长
        System.out.println("队列元素个数：" + queue.size());
        // isEmpty()方法是判断第一个节点是否为空。
        System.out.println("判断队列是否为空：" + queue.isEmpty());

        // 检查第一个元素
        System.out.println("检查队列元素：" + queue.peek());
        System.out.println("队列元素个数：" + queue.size());
    }
}
